package com.xuecheng.content.application.service.impl;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.json.JSONUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.xuecheng.base.exception.XueChengPlusException;
import com.xuecheng.base.model.PageParams;
import com.xuecheng.base.model.PageResult;
import com.xuecheng.content.application.service.CourseBaseApplication;
import com.xuecheng.content.application.vo.req.CourseBaseCreateCmd;
import com.xuecheng.content.application.vo.req.CourseBaseQry;
import com.xuecheng.content.application.vo.req.CourseBaseUpdateCmd;
import com.xuecheng.content.domain.model.dto.CourseBaseDto;
import com.xuecheng.content.domain.model.dto.CourseBaseMarketDto;
import com.xuecheng.content.application.event.CourseBaseUpdateEvent;
import com.xuecheng.content.domain.model.dto.CoursePreviewDto;
import com.xuecheng.content.domain.model.CourseBaseDo;
import com.xuecheng.content.domain.model.dto.TeachplanDto;
import com.xuecheng.content.domain.model.entity.CourseBase;
import com.xuecheng.content.domain.model.entity.CourseMarket;
import com.xuecheng.content.domain.model.entity.CoursePublishPre;
import com.xuecheng.content.domain.model.enums.CourseAuditEnum;
import com.xuecheng.content.domain.service.*;
import org.apache.commons.lang.StringUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.ApplicationEventPublisher;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.List;
import java.util.Objects;

/**
 * @Author: LiJunXi
 * @Description:
 * @Date: 2024-08-03  10:47
 */
@Service
public class CourseBaseApplicationImpl implements CourseBaseApplication {

    @Autowired
    private CourseBaseService courseBaseService;

    @Autowired
    private CourseMarketService courseMarketService;

    @Autowired
    private CourseCategoryService courseCategoryService;

    @Autowired
    private ApplicationEventPublisher applicationEventPublisher;

    @Autowired
    private TeachplanService teachplanService;

    @Autowired
    private CoursePublishPreService coursePublishPreService;

    @Override
    public PageResult<CourseBaseDto> queryCourseBaseList(PageParams pageParams, CourseBaseQry courseBaseQry) {
        //构建查询条件对象
        LambdaQueryWrapper<CourseBase> queryWrapper = new LambdaQueryWrapper<>();
        //构建查询条件，根据课程名称查询
        queryWrapper.like(StringUtils.isNotEmpty(courseBaseQry.getCourseName()), CourseBase::getName,courseBaseQry.getCourseName());
        //构建查询条件，根据课程审核状态查询
        queryWrapper.eq(StringUtils.isNotEmpty(courseBaseQry.getAuditStatus()), CourseBase::getAuditStatus,courseBaseQry.getAuditStatus());
        //构建查询条件，根据课程发布状态查询
        queryWrapper.eq(StringUtils.isNotEmpty(courseBaseQry.getPublishStatus()), CourseBase::getStatus, courseBaseQry.getPublishStatus());
        PageResult<CourseBase> result = courseBaseService.queryCourseBasePage(queryWrapper,
                new Page<>(pageParams.getPageNo(), pageParams.getPageSize()));

        return new PageResult<>(BeanUtil.copyToList(result.getItems(), CourseBaseDto.class),
                result.getCounts(), result.getPage(), result.getPageSize());
    }

    @Transactional
    @Override
    public CourseBaseDto createCourseBase(Long companyId, CourseBaseCreateCmd courseBaseCreateCmd) {
        // 保存课程信息
        CourseBase courseBase = BeanUtil.copyProperties(courseBaseCreateCmd, CourseBase.class);
        courseBase = courseBase.getDefaultInfo(courseBase, companyId);
        courseBase = courseBaseService.createCourseBase(courseBase);
        // 保存课程营销信息
        CourseMarket courseMarket = BeanUtil.copyProperties(courseBaseCreateCmd, CourseMarket.class);
        courseMarket.setId(courseBase.getId());
        courseMarketService.saveOrUpdateCourseMark(courseMarket);

        return queryCourseBaseMarket(courseBase.getId());
    }

    @Override
    public CourseBaseMarketDto queryCourseBaseMarket(Long id) {
        CourseBase courseBase = courseBaseService.getById(id);
        if (Objects.isNull(courseBase)){
            return new CourseBaseMarketDto();
        }
        CourseMarket courseMarket = courseMarketService.getById(id);
        CourseBaseMarketDto res = BeanUtil.copyProperties(courseBase, CourseBaseMarketDto.class);
        if (Objects.nonNull(courseMarket)){
            BeanUtils.copyProperties(courseMarket, res);
        }
        // 查询课程分类名称
        res.setStName(courseCategoryService.getById(courseBase.getSt()).getName());
        res.setMtName(courseCategoryService.getById(courseBase.getMt()).getName());

        return res;
    }

    @Override
    public CourseBaseDto updateCourseBase(Long companyId, CourseBaseUpdateCmd courseBaseUpdateCmd) {
        Long courseId = courseBaseUpdateCmd.getId();
        CourseBase courseBase = courseBaseService.getById(courseId);
        if (Objects.isNull(courseBase)){
            throw new XueChengPlusException("课程不存在");
        } else if (!companyId.equals(courseBase.getCompanyId())){
            throw new XueChengPlusException("本机构只能修改本机构的课程");
        }

        // 发布事件
        CourseBaseDo courseBaseDo = BeanUtil.copyProperties(courseBaseUpdateCmd, CourseBaseDo.class);
        applicationEventPublisher.publishEvent(new CourseBaseUpdateEvent(this, courseBaseDo));

        return queryCourseBaseMarket(courseId);
    }

    @Override
    public CoursePreviewDto queryCourseBasePreview(Long courseId) {
        CourseBaseMarketDto courseBaseMarketDto = this.queryCourseBaseMarket(courseId);
        List<TeachplanDto> teachplanDtos = teachplanService.queryTreeNodes(courseId);
        return new CoursePreviewDto(courseBaseMarketDto, teachplanDtos);
    }

    @Override
    public void commitAudit(Long courseId, Long companyId) {
        if (Objects.isNull(courseId)){
            throw new XueChengPlusException("课程ID不能为空");
        }

        CourseBase courseBase = courseBaseService.getById(courseId);
        if (CourseAuditEnum.SUBMIT.getCode().equals(courseBase.getAuditStatus())){
            throw new XueChengPlusException("已提交审核，请勿重复");
        }
        if (!companyId.equals(courseBase.getCompanyId())){
            throw new XueChengPlusException("权限不足");
        }

        CourseBaseMarketDto courseBaseMarketDto = queryCourseBaseMarket(courseId);
        // 课程计划
        List<TeachplanDto> teachplanDtos = teachplanService.queryTreeNodes(courseId);
        // 课程营销信息
        CourseMarket courseMarket = courseMarketService.getById(courseId);
        CoursePublishPre coursePublishPre = CoursePublishPre.buildDefault(companyId);
        BeanUtil.copyProperties(courseBaseMarketDto, coursePublishPre);
        coursePublishPre.setTeachplan(JSONUtil.toJsonStr(teachplanDtos));
        coursePublishPre.setMarket(JSONUtil.toJsonStr(courseMarket));
        courseBase.setAuditStatus(CourseAuditEnum.SUBMIT.getCode());

        // 保存或更新
        CoursePublishPre waitSave = coursePublishPreService.getById(courseId);
        if (Objects.isNull(waitSave)){
            coursePublishPreService.save(coursePublishPre);
        } else {
            coursePublishPreService.updateById(coursePublishPre);
        }
        courseBaseService.updateById(courseBase);
    }
}
